import { isEmpty, isWrapObj } from '../check/check'
const { fromJS } = require('immutable')
/**  移除字符串中指定的字符
 * @param {string} value 待处理字符串
 * @param {string} whiteSpace 要移除的字符
 * @returns {string | null} 处理之后的结果
 */
export const trimWhiteSpace = (value: string, whiteSpace: string = ' '): string | null => {
    if (!value)
        return null
    let re = new RegExp(whiteSpace, 'g')
    return value.replace(re, '')
}
/**  替换字符串中所有指定的字符
 * @param {string} value 待处理字符串
 * @param {string} from 替换的字符
 * @param {string} to  替换后的字符串
 * @returns {string | null} 处理之后的结果
 */
export const replaceAllStr = (value: string, from: string, to: string): string | null => {
    if (isEmpty(value)) {
        return null
    }
    if (!from) {
        return trimWhiteSpace(value)
    }
    let re = new RegExp(from, 'g')
    return value.replace(re, to)
}
/** 将数组转为字符串
 * @param {Array} value 待处理的数组
 * @param {string} splitValue 分隔符
 * @returns {string | null} 处理之后的结果
 */
export const transformArrToString = <T>(value: T[], splitValue: string = ''): string | null => {
    if (isEmpty(value)) {
        return null
    }
    if (value instanceof Array) {
        let tempStr = deepClone(value)?.toString()
        if (tempStr) {
            return replaceAllStr(tempStr, ',', splitValue)
        }
        return null
    }
    return null
}
/**  将字符串转为数组
 * @param {string} value 待处理的字符串
 * @param {Array} splitValue 分隔符
 * @returns {string[] | null} 处理之后的结果
 */
export const transformStringToArr = (value: string, splitValue?: string): string[] | null => {
    if (isEmpty(value)) {
        return null
    }
    return splitValue ? value.split(splitValue) : [value]
}
/** 将字驼峰命名的字符串转为下划线分割的字符串
 * @param {string} value 待处理的字符串
 * @returns {string | null} 处理之后的结果
 */
export const transformCamelToUnderline = (value: string): string | null => {
    if (isEmpty(value)) {
        return null
    }
    return value.replace(/([A-Z])/g, '_$1').toLowerCase()
}
/** 将下划线分割命名的字符串转为驼峰的字符串
 * @param {string} value 待处理的字符串
 * @returns {string | null} 处理之后的结果
 */
export const transformUnderlineToCamel = (value: string): string | null => {
    if (isEmpty(value)) {
        return null
    }
    return value.replace(/\_(\w)/g, function (_all, letter) {
        return letter.toUpperCase();
    });
}
/** 获取地址栏参数
 * @param {string} name 要获取的参数
 * @returns {string | null} 获取到的指定的参数值
 */
export const getUrlParam = (name: string): string | null => {
    // 构造一个含有目标参数的正则表达式对象
    const reg = new RegExp('(^|&)' + name + '=([^&]*)(&|$)')
    // 匹配目标参数
    const r = window.location.search.substring(1).match(reg)
    return r !== null ? decodeURI(r[2] || '') : null
}
/** 移除对象的指定的属性
 * @param { T } obj 待删除属性的对象
 * @param { string } propertyName 要删除的属性
 * @returns { T | null } 删除之后的结果，失败返回Null
 */
export const deleteObjectProperty = <T>(obj: T, propertyName: keyof T): T | null => {
    // if target is wrap class return null
    if (isWrapObj(obj)) {
        return null
    }
    // deep copy source obj
    const tempObj = deepClone(obj)
    if (!tempObj) {
        return null
    }
    // delete target property
    delete tempObj[propertyName]
    return tempObj
}
/** 删除空属性
 * @param { T } obj  待删除属性的对象
 * @returns { T | null} 删除之后的结果，失败返回Null
 */
export const deleteEmptyProperty = <T>(obj: T): T | null => {
    // if target is wrap class return null
    if (isWrapObj(obj)) {
        return null
    }
    // create source clone
    let tempObj = deepClone(obj)
    if (tempObj) {
        for (const key in tempObj) {
            if (isEmpty(tempObj[key])) {
                delete tempObj[key]
            }
        }
    }
    return tempObj
}
/** 格式化金额，三位一逗号
 * @param {string | number} str  待格式化的金额
 * @param {string} identifier 分隔符
 * @returns {string} 格式化之后的金额
 */
export const formatAmount = (str: string | number, identifier: string = ','): string => {
    if (str && str != null) {
        str = String(str);
        let left = str.split('.')[0] || ''
        let right = str.split('.')[1] || '';
        right = right ? (right.length >= 2 ? '.' + right.substring(0, 2) : '.' + right + '0') : '.00';
        let temp = left.split('').reverse().join('').match(/(\d{1,3})/g) || [];
        return (Number(str) < 0 ? "-" : "") + temp.join(identifier).split('').reverse().join('') + right;
    } else if (str === 0) {
        return '0.00';
    } else {
        return "";
    }
};

//深拷贝
export const deepCopy = (data: any, hash = new WeakMap()) => {
    if (typeof data !== 'object' || data === null) {
        throw new TypeError('传入参数不是对象')
    }
    // 判断传入的待拷贝对象的引用是否存在于hash中
    if (hash.has(data)) {
        return hash.get(data)
    }
    const newData: any = {};
    const dataKeys = Object.keys(data);
    dataKeys.forEach(value => {
        const currentDataValue = data[value];
        // 基本数据类型的值和函数直接赋值拷贝 
        if (typeof currentDataValue !== "object" || currentDataValue === null) {
            newData[value] = currentDataValue;
        } else if (Array.isArray(currentDataValue)) {
            // 实现数组的深拷贝
            newData[value] = [...currentDataValue];
        } else if (currentDataValue instanceof Set) {
            // 实现set数据的深拷贝
            newData[value] = new Set([...currentDataValue]);
        } else if (currentDataValue instanceof Map) {
            // 实现map数据的深拷贝
            newData[value] = new Map([...currentDataValue]);
        } else {
            // 将这个待拷贝对象的引用存于hash中
            hash.set(data, data)
            // 普通对象则递归赋值
            newData[value] = deepCopy(currentDataValue, hash);
        }
    });
    return newData;
}
/** 深拷贝
 * @param source wait for copy
 * @returns after copy obj
 */
export const deepClone = <T>(source: T): T | null => {
    if (!source || typeof source !== 'object') {
        return null
    }
    // if target is wrap class return null
    if (isWrapObj(source)) {
        return null
    }
    return fromJS(source).toJS()
}

export function useForm(searchData: any) {
    const deepForm = (params?: any) => JSON.parse(JSON.stringify(params ? params : searchData))
  return {
    cacheForm: searchData,
    deepForm: deepForm,
  }
}
